extends Control
 
@export var menuItemWidth = 30
@export var menuItemHeight = 8

var battleField:BattleField
var containerArr:Array = []
var containerDict:Dictionary = {}
var containerPosDict:Dictionary = {}
var containerDepthDict:Dictionary = {}

var rightStartPos
var leftStartPos


func initAndShow(menuItems:Array):
	containerDepthDict = {}
	containerArr = []
	containerDict = {}
	
	initMenuItems(menuItems, 0, "topMost")
	initContainersPos()
	
	containerDict["topMost"].showAll()
	containerDepthDict[0] = containerDict["topMost"]
	
	set_physics_process(true)
	

func initMenuItems(menuItemsData:Array, depth, parentMenuItemName):
	var container:BattleEntityCommandBoxContainer = Global.createSceneInst("BattleEntityCommandBoxContainer")
	add_child(container)
	container.commandBox = self
	containerArr.append(container)
	containerDict[parentMenuItemName] = container
	container.init(menuItemsData, depth, parentMenuItemName)
	container.hideAll()
	
	for menuItemData in menuItemsData:
		if menuItemData.subMenuItemsData.size() > 0:
			initMenuItems(menuItemData.subMenuItemsData, depth + 1, menuItemData.name)
			
			
func initContainersPos():
	containerPosDict = {}
	
	rightStartPos = Vector2(battleField.currentSelectedHeroInst.position.x + battleField.cellSize / 2.0, battleField.currentSelectedHeroInst.position.y - battleField.cellSize / 2.0)
	leftStartPos = Vector2(battleField.currentSelectedHeroInst.position.x - battleField.cellSize / 2.0, battleField.currentSelectedHeroInst.position.y - battleField.cellSize / 2.0)
	
	var isRight = true
	for container in containerArr:
		var tentativeTargetPosX = rightStartPos.x + container.depth * (container.containerSize.x + 1)
		var tentativeTargetPosY = rightStartPos.y - container.containerSize.y / 2.0
		var withinViewX = isWithinViewX(Vector2(tentativeTargetPosX + container.containerSize.x, tentativeTargetPosY))
		if not withinViewX:
			isRight = false
			break
	
	for container in containerArr:
		var tentativeTargetPosX = rightStartPos.x + container.depth * (container.containerSize.x + 1)
		var tentativeTargetPosY = rightStartPos.y - container.containerSize.y / 2.0
		if not isRight:
			tentativeTargetPosX = leftStartPos.x - (container.depth + 1) * (container.containerSize.x + 1)
		
		var viewPos = Global.worldPos2ViewPos(Vector2(tentativeTargetPosX, tentativeTargetPosY), battleField.cam)
		if viewPos.y < 0:
			tentativeTargetPosY -= viewPos.y
			
		viewPos = Global.worldPos2ViewPos(Vector2(tentativeTargetPosX, tentativeTargetPosY + container.containerSize.y), battleField.cam)
		if viewPos.y >= Global.viewportHeight:
			tentativeTargetPosY -= (viewPos.y - Global.viewportHeight)
		
		containerPosDict[container] = Vector2(tentativeTargetPosX, tentativeTargetPosY)
		container.position = containerPosDict[container]
		

func isWithinViewX(worldPos):
	var viewPos = Global.worldPos2ViewPos(worldPos, battleField.cam)
	if viewPos.x >= Global.viewportWidth or viewPos.x < 0:
		return false
	return true


func onMenuItemClick(inst):
	if inst.hasSubMenuitem():
		var targetContainer = containerDict[inst.data.name]
		var depth = targetContainer.depth
		
		if containerDepthDict.has(depth):
			containerDepthDict[depth].hideAll()
			containerDepthDict.erase(depth)
		
		targetContainer.showAll()
		containerDepthDict[depth] = targetContainer
	else:
		print("click menuitem ", inst.data.name)
		if inst.data.name == "取消":
			onCancelCommandBox()
		else:
			battleField.onExecuteCommand(inst.data.name, inst.data)
		hideAllContainer()
		
	
func _physics_process(delta):
	processCancel()
	

func hideAllContainer():
	var depth = 3
	for index in range(depth, -1, -1):
		if not containerDepthDict.has(index): continue
		
		containerDepthDict[index].hideAll()
		containerDepthDict.erase(index)
		
	set_physics_process(false)


func processCancel():
	if Input.is_action_just_pressed("mouse_right_button"):
		var depth = 3
		for index in range(depth, -1, -1):
			if not containerDepthDict.has(index): continue
			
			containerDepthDict[index].hideAll()
			containerDepthDict.erase(index)
			
			if index == 0:
				set_physics_process(false)
				onCancelCommandBox()
			
			break
			

func onCancelCommandBox():
	print("onCancelCommandBox")
	battleField.onCancelCommandBox()






